package com.example.administrator.newxlmedical;

import android.content.SharedPreferences;
import android.graphics.drawable.AnimationDrawable;
import android.media.MediaPlayer;
import android.os.Bundle;
import android.os.Message;
import android.text.TextUtils;
import android.util.Base64;
import android.util.Log;
import android.view.View;
import android.widget.ImageView;
import android.widget.RelativeLayout;
import android.widget.TextView;

import com.irisian.irissdk.IdentifyListener;
import com.irisian.irissdk.IdentifyResult;
import com.irisian.irissdk.IrisSdk;
import com.irisian.irissdk.ReadDistanceCallBack;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.Iterator;
import java.util.Map;
import java.util.Set;

import beans.NewUserInfoBean;
import butterknife.BindView;
import butterknife.ButterKnife;
import butterknife.OnClick;
import constants.Constants;
import constants.HandlerConstant;
import customhandler.MyHandler;
import netframe.GetRetrofit;
import netframe.MyAction1;
import netframe.NetAddress;
import netframe.NetReconnectFunc1;
import rx.Observable;
import rx.android.schedulers.AndroidSchedulers;
import rx.functions.Action1;
import rx.functions.Func1;
import rx.observables.GroupedObservable;
import rx.schedulers.Schedulers;
import singleton.SingletonClass;
import utils.IrisUtil;
import utils.ObjectSaveUtil;
import utils.SharedPreferenceUtil;
import utils.ToastUtil;

public class IrisEnterActivity extends BaseEnterActivity {

    @BindView(R.id.iv_iris_enter_close)
    ImageView ivClose;
    @BindView(R.id.rl_iris_enter)
    RelativeLayout rlIrisEnter;
    @BindView(R.id.iv_iris_enter_loading)
    ImageView ivIrisEnterLoading;
    @BindView(R.id.rl_iris_enter_loading)
    RelativeLayout rlIrisEnterLoading;
    @BindView(R.id.tv_iris_enter_loading_text)
    TextView tvLoadingText;
    @BindView(R.id.tv_iris_enter_loading_text_point)
    TextView tvPoint;
    @BindView(R.id.iv_iris_enter)
    ImageView ivIrisEnter;
    @BindView(R.id.tv_iris_enter_error_content)
    TextView tvErrorContent;
    private ArrayList<IdentifyResult> list = new ArrayList<>();//虹膜验证成功的次数,会多次回调
    private ArrayList<byte[]> left_code_list = new ArrayList<>();//保存左眼虹膜
    private ArrayList<byte[]> right_code_list = new ArrayList<>();//保存右眼虹膜
    private MyHandler allHandler;
    private Map<Integer, byte[]> map = new HashMap<>();
    private String changeTime;
    private SharedPreferences sp;
    private AnimationDrawable animationDrawable;
    private MediaPlayer mediaPlayer;
    private boolean isFrist = true;
    private int count;
    private boolean aa;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_iris_enter);
        ButterKnife.bind(this);

        ivIrisEnterLoading.setBackgroundResource(R.drawable.loading);

        animationDrawable = (AnimationDrawable) ivIrisEnterLoading.getBackground();
        animationDrawable.start();

        allHandler = SingletonClass.getSingleton(MyHandler.class);

        allHandler.removeMessages(HandlerConstant.NO_OPERATION);
        sp = SharedPreferenceUtil.getSharedPreferences(this);
        changeTime = sp.getString(Constants.LRIS_USER_BEAN_CHANGETIME, "");

        Map<Integer, byte[]> readMap = (Map<Integer, byte[]>) ObjectSaveUtil.readObject(this, Constants.LRIS_LOGIN_DATA, Constants.LRIS_LOGIN_DATA);
        if (readMap != null) {
            map.putAll(readMap);
        }
        getIris();
    }

    @Override
    protected void onDestroy() {
        super.onDestroy();
        animationDrawable.stop();
        if (IrisSdk.isInitialized()) {
            IrisSdk.stopReadDistance(IrisEnterActivity.this);
            IrisSdk.closeCamera(IrisEnterActivity.this);
            IrisSdk.releaseSdk(IrisEnterActivity.this);
        }
    }

    @OnClick(R.id.iv_iris_enter_close)
    public void onViewClicked() {
        finish();
    }

    //获取所有用户虹膜
    private void getIris() {
        String sql;
        if (TextUtils.isEmpty(changeTime)) {
            Log.e(TAG, "getIris: null");
            sql = "select LeftImg,ID,ChangeTime from UserInfo where LeftImg is not null and Enable = 'True' and DelFlag = 0 order by ChangeTime asc";
        } else {
            Log.e(TAG, "getIris: no null");
            sql = "select LeftImg,ID,ChangeTime from UserInfo where LeftImg is not null and Enable = 'True' and DelFlag = 0 and ChangeTime > '" + changeTime + "' order by ChangeTime asc";
        }
        GetRetrofit.getInstance().getUserInfo2(NetAddress.token, NetAddress.machineCode, sql).subscribeOn(Schedulers.io())
                .retryWhen(new NetReconnectFunc1())
                .groupBy(new Func1<NewUserInfoBean, Boolean>() {
                    @Override
                    public Boolean call(NewUserInfoBean newUserInfoBean) {
                        return newUserInfoBean.getData() == null ? false : newUserInfoBean.getData().size() > 0;
                    }
                }).observeOn(AndroidSchedulers.mainThread()).flatMap(new Func1<GroupedObservable<Boolean, NewUserInfoBean>, Observable<NewUserInfoBean.DataBean>>() {
            @Override
            public Observable<NewUserInfoBean.DataBean> call(GroupedObservable<Boolean, NewUserInfoBean> booleanUserInfoBeanGroupedObservable) {
                if (booleanUserInfoBeanGroupedObservable.getKey()) {
                    return booleanUserInfoBeanGroupedObservable.observeOn(Schedulers.io()).flatMap(new Func1<NewUserInfoBean, Observable<NewUserInfoBean.DataBean>>() {
                        @Override
                        public Observable<NewUserInfoBean.DataBean> call(NewUserInfoBean newUserInfoBean) {
                            left_code_list.clear();
                            right_code_list.clear();
                            list.clear();
                            return Observable.from(newUserInfoBean.getData()).doOnNext(new Action1<NewUserInfoBean.DataBean>() {
                                @Override
                                public void call(NewUserInfoBean.DataBean dataBean) {
                                    if (!TextUtils.isEmpty(dataBean.getLeftImg())) {

                                        byte[] leftByte = Base64.decode(dataBean.getLeftImg(), Base64.DEFAULT);
                                        left_code_list.add(leftByte);
                                        right_code_list.add(leftByte);

                                        map.put(dataBean.getID(), leftByte);

                                        SharedPreferences.Editor edit = sp.edit();
                                        edit.putString(Constants.LRIS_USER_BEAN_CHANGETIME, dataBean.getChangeTime());
                                        edit.commit();
                                    }
                                }
                            }).last();
                        }
                    });
                } else {
                    if (map.size() != 0) {
                        initIris();
                    } else {
                        ToastUtil.showToast(IrisEnterActivity.this, "暂无用户");
                    }
                    return null;
                }
            }
        }).observeOn(AndroidSchedulers.mainThread()).subscribe(new Action1<NewUserInfoBean.DataBean>() {
            @Override
            public void call(NewUserInfoBean.DataBean dataBean) {
                ObjectSaveUtil.saveObject(IrisEnterActivity.this, map, Constants.LRIS_LOGIN_DATA, Constants.LRIS_LOGIN_DATA);
                initIris();
            }
        }, new MyAction1() {
            @Override
            public void call(Throwable throwable) {
                animationDrawable.stop();
                rlIrisEnter.setVisibility(View.VISIBLE);
                rlIrisEnterLoading.setVisibility(View.GONE);
                ToastUtil.showToast(IrisEnterActivity.this, "网络请求错误");
            }
        });
    }

    @Override
    protected void onHandleMessage(Message msg) {
        super.onHandleMessage(msg);

        switch (msg.what) {
            case HandlerConstant.IRIS_LOGIN_NO_USER:
                rlIrisEnter.setVisibility(View.VISIBLE);
                rlIrisEnterLoading.setVisibility(View.GONE);
                ivIrisEnter.setImageResource(R.mipmap.noneuser);
                tvErrorContent.setText("用户不存在!");
                break;
            case HandlerConstant.IRIS_LOGIN_ERROR:
                rlIrisEnter.setVisibility(View.VISIBLE);
                rlIrisEnterLoading.setVisibility(View.GONE);
                ivIrisEnter.setImageResource(R.mipmap.noneuser);
                tvErrorContent.setText("您已被禁用!");

                if (IrisSdk.isInitialized()) {
                    IrisSdk.stopReadDistance(IrisEnterActivity.this);
                    IrisSdk.closeCamera(IrisEnterActivity.this);
                    IrisSdk.releaseSdk(IrisEnterActivity.this);
                }

                break;

            case HandlerConstant.IRIS_ENTER_LOADING:
                count++;
                if (count == 1) {
                    tvPoint.setText(".");
                } else if (count == 2) {
                    tvPoint.setText(". .");
                } else if (count == 3) {
                    tvPoint.setText(". . .");
                } else if (count == 4) {
                    tvPoint.setText(". . . .");
                } else if (count == 5) {
                    tvPoint.setText(". . . . .");
                } else if (count == 6) {
                    tvPoint.setText(". . . . . .");
                    count = 0;
                }
                sendEmptyMessageDelay(HandlerConstant.IRIS_ENTER_LOADING, 300);
                break;

            case HandlerConstant.IRIS_LOGIN_ERROR_AGIN :
                ToastUtil.showToast(IrisEnterActivity.this,"登录失败，请退出重新登录!");
                rlIrisEnter.setVisibility(View.VISIBLE);
                rlIrisEnterLoading.setVisibility(View.GONE);
                break;

            case HandlerConstant.IRIS_UNLOGIN_TIME :
                finish();
                break;

        }
    }

    //初始化虹膜
    private void initIris() {
        Set set = map.entrySet();
        Iterator iterator = set.iterator();

        while (iterator.hasNext()) {
            Map.Entry mapentry = (Map.Entry) iterator.next();
            byte[] data = (byte[]) mapentry.getValue();
            left_code_list.add(data);
            right_code_list.add(data);
        }

        IrisUtil.initSdk(IrisEnterActivity.this);
        boolean isOpenCamera = IrisSdk.openCamera(IrisEnterActivity.this);
        aa = true;
        if (isOpenCamera) {
            sendEmptyMessageDelay(HandlerConstant.IRIS_UNLOGIN_TIME, UNLOGIN_TIME);
            IrisSdk.startReadDistance(IrisEnterActivity.this, new ReadDistanceCallBack() {
                @Override
                public void onReadDistance(int i) {
                    //  i == 2 时 绿灯   0 灯灭   1、3 红灯
                }
            });
            startIdentify(left_code_list, right_code_list);
        } else {
            animationDrawable.stop();
            rlIrisEnter.setVisibility(View.VISIBLE);
            rlIrisEnterLoading.setVisibility(View.GONE);

            ToastUtil.showToast(IrisEnterActivity.this, "打开摄像头失败，请重新点击登陆");
        }

    }

    //开始验证
    private void startIdentify(final ArrayList<byte[]> leftList, final ArrayList<byte[]> rightList) {
        animationDrawable.stop();
        rlIrisEnter.setVisibility(View.VISIBLE);
        rlIrisEnterLoading.setVisibility(View.GONE);

        IrisSdk.setIrisCodeList(true, leftList.size(),
                leftList.toArray(new byte[leftList.size()][IrisSdk.getConfiguration().IRIS_TEMPLATE_LENGTH]));
        IrisSdk.setIrisCodeList(false, rightList.size(),
                rightList.toArray(new byte[rightList.size()][IrisSdk.getConfiguration().IRIS_TEMPLATE_LENGTH]));
        IrisSdk.startIdentify(new IdentifyListener() {
            @Override
            public boolean onIdentifySuccess(IdentifyResult identifyResult) {
                if (isFrist) {
                    isFrist = false;
                    runOnUiThread(new Runnable() {
                        @Override
                        public void run() {
                            rlIrisEnter.setVisibility(View.GONE);
                            ivIrisEnterLoading.setVisibility(View.GONE);
                            tvLoadingText.setText("登录中,请稍等");
                            rlIrisEnterLoading.setVisibility(View.VISIBLE);
                            sendEmptyMessage(HandlerConstant.IRIS_ENTER_LOADING);
                        }
                    });
//                synchronized (list) {
                    Log.e(TAG, "onIdentifySuccess: ");
                    if (identifyResult.is_left) {
                        list.add(identifyResult);
                        if (list.size() == 1) {
                            String code = Base64.encodeToString(leftList.get(identifyResult.code_index), Base64.DEFAULT);
                            userLogin("select ID,Name,UCode,SubTime,DelFlag,Department,Enable,RoleInfoId from UserInfo where LeftImg = '" + code + "'", 2);
                            getCabinetInfoId();
                        }
                    } else {
                        list.add(identifyResult);
                        if (list.size() == 1) {
                            String code = Base64.encodeToString(rightList.get(identifyResult.code_index), Base64.DEFAULT);
                            userLogin("select ID,Name,UCode,SubTime,DelFlag,Department,Enable,RoleInfoId from UserInfo where RightImg = '" + code + "'", 2);
                            getCabinetInfoId();
                        }
                    }
                }
                return true;
            }

            @Override
            public void onIdentifyFailure(boolean b, int i, String s) {
                runOnUiThread(new Runnable() {
                    @Override
                    public void run() {
                        mHandler.removeMessages(HandlerConstant.IRIS_UNLOGIN_TIME);

                        try {
                            Thread.sleep(100);
                        } catch (InterruptedException e) {
                            e.printStackTrace();
                        }

                        //若资源被释放,则没有识别失败的提示音（上面延时，是为了让提示音先播放，在释放）
                        IrisSdk.stopReadDistance(IrisEnterActivity.this);
                        IrisSdk.closeCamera(IrisEnterActivity.this);

                    }
                });
            }
        });
    }


}
